library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;

entity ps2_kb_wdt is
  generic (
    CTR_LEN : positive := 16
  );
  port (
    reset   : in std_logic;
    clock   : in std_logic;

    start   : in std_logic;
    stop    : in std_logic;

    timeout : out std_logic
  );
end entity ps2_kb_wdt;

architecture default of ps2_kb_wdt is
  type state_t is (IDLE, COUNT);

  signal state_reg : state_t;
  signal state_nxt : state_t;

  signal ctr_reg : unsigned (CTR_LEN - 1 downto 0);
  signal ctr_nxt : unsigned (CTR_LEN - 1 downto 0);
begin
  process (reset, clock) is
  begin
    if reset = '1' then
      state_reg <= IDLE;
      ctr_reg <= (ctr_reg'range => '0');
    elsif rising_edge (clock) then
      state_reg <= state_nxt;
      ctr_reg <= ctr_nxt;
    end if;
  end process;

  process (state_reg, ctr_reg, start, stop) is
  begin
    state_nxt <= state_reg;
    ctr_nxt <= ctr_reg - 1;
    timeout <= '0';

    case state_reg is
      when IDLE =>
        if start = '1' then
          state_nxt <= COUNT;
          ctr_nxt <= (ctr_nxt'range => '1');
        end if;
      when COUNT =>
        if stop = '1' then
          state_nxt <= IDLE;
        end if;
        if ctr_reg = (ctr_reg'range => '0') then
          timeout <= '1';
          state_nxt <= IDLE;
        end if;
    end case;
  end process;

end architecture default;
